你要和平还是尊严?和平就是屈服,尊严就是死。
概述
Python的Queue队列,主要用于多生产者和消费者模式下的队列实现,特别适合多线程时的消息交换。通过使用队列,把生产者和消费者分解开来,作为其中的中间件,比如生产者产生一个数据,然后放到queue队列中,queue队列在把这个数据放到消费者线程中。使用单线程不必用队列,但是队列对于多线程来说是不可或缺的。
它实现了常见的锁语法,临时阻塞线程,防止竞争,这有赖于Python对线程的支持。
Queue三种模式
FIFO模式
FIFO模式就是管道模式,就像一根管道一样,数据一个一个的进去,然后一个一个的出来,你可以设置这个管道运行进入数据的个数,然后数据进满了之后,一个一个数据出来,出来后又进数据。
LIFO模式
LIFO模式是后进先出模式,也就是堆栈,元素只能在栈顶堆入。就是后进的数据先出去,先进的数据最后出去。递归函数就是用的堆栈。
优先级队列
优先级队列的每个数据都带有一个优先值,优先值越小的越早出去,优先值相同的先放入队列的先出去。
三种模式使用方法
FIFO模式
使用方法
q1=Queue.Queue(maxsize=0)
maxsize表示队列中最多有多少个数据,数据堆满了后,堵塞队列,然后数据一个一个的出去。如果设置0表示队列的元素不设上限,可以有无数个数据,但是需要当心内存溢出。
LIFO模式
使用方法
q2=Queue.LifoQueue(maxsize=0)
这里的maxsize和上面的意义一样,但是LifoQueue()是先进后出模式,也就是说先进去的最后出来,有点像倒序的意思。
优先级模式
使用方法
q3=Queue.PriorityQueue(maxsize=0)
优先级模式,这里的元素优先顺序是按照sorted(list(entries))[0]的接过来定义的,而元素的结构形式通常是(priority_number,data)这样的元祖。
放入数据与取出数据
q=Queue.Queue(maxsize=10)
# 首先确定使用的模式,内部最多存储10个元素
q.put(x,block=True,timeout=None)
# 这里放入一个数据x,字符串数字都可以,一般来说不要修改配置,使用默认的就可以,直接q.put(x)。block=True表示队列堵塞,直到队列有空的地方出来再把元素传进去,timeout=10表示10秒后如果没有新的元素传进去就报错。
q.get(x,block=True,timeout=None)
# 这里是把数据x取出来,一般使用默认配置就好,知己q.get(x)。如果设置block=True,timeout=10,就是说如果10秒没有接收到数据就直接报错,如果设置block=False的话,timeout参数会被忽略,此时就是只要队列有元素就直接弹出这个元素,没有元素就直接报错。
其他对象
当队列空的时候
print q.Empty()
# 如果队列是空的就返回TRUE
判断队列是否为空这种很常用,如果队列的数据如果不为空,那么就执行后面的消费者,取出数据给消费者对象。
while not q.Empty():
# 如果队列中还有数据的话
print abs(q.get(x))
# 获取队列的元素,打印出元素的绝对值。这里只是一个演示,一般会把q.get(x)传入一个函数中。
获取队列元素个数
print q.qsize()
队列是否满了
print q.full()
# 如果满了返回TRUE
堵塞调用进程
q.join()
阻塞调用线程,直到队列中的所有任务被处理掉。
只要有数据被加入队列,未完成的任务数就会增加。当消费者线程调用task_done()(意味着有消费者取得任务并完成任务),未完成的任务数就会减少。当未完成的任务数降到0,join()解除阻塞。
队列任务完成
q.task_done()
意味着之前入队的一个任务已经完成。由队列的消费者线程调用。每一个get()调用得到一个任务,接下来的task_done()调用告诉队列该任务已经处理完毕。
如果当前一个join()正在阻塞,它将在队列中的所有任务都处理完时恢复执行(即每一个由put()调用入队的任务都有一个对应的task_done()调用)。
代码实例1,不设置maxsize
list1=[1,2,3,4,5,6,7,8,9]
q=Queue.Queue()
#管道模式正序
for x in list1:
q.put(x)
# 把元素一个一个加载进管道中
while not q.empty():
# 当管道的元素不为空的时候
print q.get(x)
# 打印出元素
print 'queue size:' + str(q.qsize())
# 打印队列中还剩下多少元素
运行结果:
1
queue size:8
2
queue size:7
3
queue size:6
4
queue size:5
5
queue size:4
6
queue size:3
7
queue size:2
8
queue size:1
9
queue size:0
代码实例2,设置maxsize
前面说过maxsize表示队列中最多有多少个数据,数据堆满了后,堵塞队列,然后数据一个一个的出去。
list1=[1,2,3,4,5,6,7,8,9]
q=Queue.Queue(maxsize=5)
#管道内最多存在5个
for x in list1:
q.put(x)
# 管道内载入5个元素了
while not q.empty():
print q.get(x)
print 'queue size:' + str(q.qsize())
# 执行完了这5个元素
q.task_done()
q.join()
#task_done和join()可以不加上去,至于两种用法看看上面写的
运行结果一致